
<template>
  <div ref="container" class="three-container-class"></div>
  <div ref="touchAreaEl" class="touch-area-class"></div>
</template>

<script setup lang="ts">
import { ref, onMounted, onUnmounted, reactive, defineProps, defineExpose, nextTick } from "vue";
import PureWind from "./PureWind";
declare global {
  interface Window {
    pureInputPercents: Array<{x: number, y: number}>;
    Android?: {
      onPureTouchEvent?: (json: string) => void;
      // 你可以根据实际情况添加更多方法声明
    };
  }
}

const props = defineProps({
  instanceIndex: {
    type: Number,
    required: true
  }
});


const container = ref<HTMLElement | null>(null);
const touchAreaEl = ref<HTMLElement | null>(null);

let windInstance: PureWind | null = null;
let animationFrameId: number | null = null;
let lastRender = 0;
const FPS = 40;

const mouseState = reactive({
  isDragging: false,
  startX: 0,
  startY: 0,
  startPercentX: 0,
  startPercentY: 0,
  deltaX: 0,
  deltaY: 0,
});

const handleMouseDown = (event: MouseEvent | TouchEvent) => {
  if (!windInstance) return;
  mouseState.isDragging = true;

  let clientX, clientY;
  if ("touches" in event) {
    clientX = event.touches[0].clientX;
    clientY = event.touches[0].clientY;
    window.addEventListener("touchmove", handleMouseMove, { passive: false });
    window.addEventListener("touchend", handleMouseUp);
  } else {
    clientX = event.clientX;
    clientY = event.clientY;
    window.addEventListener("mousemove", handleMouseMove);
    window.addEventListener("mouseup", handleMouseUp);
  }
  mouseState.startX = clientX;
  mouseState.startY = clientY;

  mouseState.startPercentX = windInstance.test_input_percent_x;
  mouseState.startPercentY = windInstance.test_input_percent_y;
    // 通知安卓WebView
  if (window.Android && typeof window.Android.onPureTouchEvent === 'function') {
    window.Android.onPureTouchEvent(JSON.stringify({
      type: 'down',
      index: props.instanceIndex,
      x: clientX,
      y: clientY
    }));
  }
};

const handleMouseMove = (event: MouseEvent | TouchEvent) => {
  if (mouseState.isDragging && windInstance) {
    let currentX, currentY;
    if ("touches" in event) {
      event.preventDefault();
      currentX = event.touches[0].clientX;
      currentY = event.touches[0].clientY;
    } else {
      currentX = event.clientX;
      currentY = event.clientY;
    }
    mouseState.deltaX = currentX - mouseState.startX;
    mouseState.deltaY = currentY - mouseState.startY;

    windInstance.test_input_percent_x = mouseState.startPercentX + mouseState.deltaX;
    windInstance.test_input_percent_y = mouseState.startPercentY - mouseState.deltaY;
        // 通知安卓WebView
    if (window.Android && typeof window.Android.onPureTouchEvent === 'function') {
      window.Android.onPureTouchEvent(JSON.stringify({
        type: 'move',
        index: props.instanceIndex,
        x: windInstance.test_input_percent_x,
        y: windInstance.test_input_percent_y
      }));
    }
  }
};

const handleMouseUp = (event: MouseEvent | TouchEvent) => {
  if (!mouseState.isDragging) return;
  mouseState.isDragging = false;
  if ("touches" in event) {
    window.removeEventListener("touchmove", handleMouseMove);
    window.removeEventListener("touchend", handleMouseUp);
  } else {
    window.removeEventListener("mousemove", handleMouseMove);
    window.removeEventListener("mouseup", handleMouseUp);
  }
    // 通知安卓WebView
  if (window.Android && typeof window.Android.onPureTouchEvent === 'function') {
    window.Android.onPureTouchEvent(JSON.stringify({
      type: 'up',
      index: props.instanceIndex,
      x: 0,
      y: 0
    }));
  }
};

const animate = (now?: number) => {
  if (windInstance) {
    const currentTime = now || performance.now();
    if (!lastRender || currentTime - lastRender >= 1000 / FPS) {
      windInstance.update();
      lastRender = currentTime;
            // 每帧同步到全局
    if (window.pureInputPercents) {
        window.pureInputPercents[props.instanceIndex] = {
          x: windInstance.test_input_percent_x,
          y: windInstance.test_input_percent_y
        };
      }
    }
    animationFrameId = requestAnimationFrame(animate);
  }
};

let resizeObserver: ResizeObserver | null = null;

onMounted(async () => {
  await nextTick(); 
  if (container.value) {
    windInstance = new PureWind(container.value);
    animate();
    if (!window.pureInputPercents) {
      window.pureInputPercents = [];
    }

    const handleResize = () => {
      if (windInstance && container.value) {
        windInstance.resize(
          container.value.clientWidth,
          container.value.clientHeight
        );
      }
    };

    // Initial resize
    handleResize(); 
    
    // Use ResizeObserver for more robust instance-specific resize handling
    resizeObserver = new ResizeObserver(handleResize);
    resizeObserver.observe(container.value);

    if (touchAreaEl.value) {
      touchAreaEl.value.addEventListener("mousedown", handleMouseDown);
      touchAreaEl.value.addEventListener("touchstart", handleMouseDown, { passive: false });
    } else {
      console.warn(`Touch area for Pure instance ${props.instanceIndex} not found.`);
    }
  } else {
    console.error(`Container for Pure instance ${props.instanceIndex} not found.`);
  }
});

onUnmounted(() => {
  if (animationFrameId !== null) {
    cancelAnimationFrame(animationFrameId);
    animationFrameId = null;
  }

  if (touchAreaEl.value) {
    touchAreaEl.value.removeEventListener("mousedown", handleMouseDown);
    touchAreaEl.value.removeEventListener("touchstart", handleMouseDown);
  }

  // 清理全局监听器，防止重复绑定
  window.removeEventListener("mousemove", handleMouseMove);
  window.removeEventListener("mouseup", handleMouseUp);
  window.removeEventListener("touchmove", handleMouseMove);
  window.removeEventListener("touchend", handleMouseUp);

  if (resizeObserver && container.value) {
    resizeObserver.unobserve(container.value);
  }
  resizeObserver = null;

  if (windInstance) {
    windInstance.dispose();
    windInstance = null;
  }

  // 彻底移除canvas，防止Three.js残留
  if (container.value) {
    container.value.innerHTML = "";
  }
});

const getTouchAreaRect = () => {
  return touchAreaEl.value ? touchAreaEl.value.getBoundingClientRect() : null;
};

const getContainerRect = () => {
  return container.value ? container.value.getBoundingClientRect() : null;
}

defineExpose({

  getTouchAreaRect,
  getContainerRect,
});


</script>

<style>
.three-container-class {
  width: 100%;
  height: 100%;
  position: relative; 
  background: transparent !important;
  overflow: visible;
}

.touch-area-class {
  position: absolute;
  left: 50%;
  top: 50%;
  width: 50%; /* 几乎与three-container同宽，留2%边距防止溢出 */
  height: 70%; /* 占Pure组件高度的70% */
  /* border: 2px solid #fff; */
  box-sizing: border-box;
  z-index: 10;
  background: rgba(255,255,255,0.0); 
  transform: translate(-50%, -50%);
  cursor: grab;
  border-radius: 8px;
  pointer-events: auto;
  display: flex;
  align-items: center;
  justify-content: center;
}
</style>

        